package com.farm.project.service.impl;

import com.farm.project.domain.Field;
import com.farm.project.domain.ProjectGradation;
import com.farm.project.domain.ProjectType;
import com.farm.project.domain.ProjectTypeGradation;
import com.farm.core.time.TimeTool;

import org.apache.commons.lang.StringUtils;
import org.apache.log4j.Logger;

import com.farm.project.dao.FieldRePtypeDaoInter;
import com.farm.project.dao.ProjectGradationDaoInter;
import com.farm.project.dao.ProjectTypeDaoInter;
import com.farm.project.dao.ProjectTypeGradationDaoInter;
import com.farm.project.service.ProjectTypeServiceInter;
import com.farm.web.WebUtils;
import com.farm.core.sql.query.DBRule;
import com.farm.core.sql.query.DBRuleList;
import com.farm.core.sql.query.DBSort;
import com.farm.core.sql.query.DataQuery;
import com.farm.core.sql.result.DataResult;

import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import javax.annotation.Resource;

import com.farm.core.auth.domain.LoginUser;

/* *
 *功能：项目分类服务层实现类
 *详细：
 *
 *版本：v0.1
 *作者：FarmCode代码工程
 *日期：20150707114057
 *说明：
 */
@Service
public class ProjectTypeServiceImpl implements ProjectTypeServiceInter {
	@Resource
	private ProjectTypeDaoInter projecttypeDaoImpl;
	@Resource
	private ProjectGradationDaoInter projectgradationDaoImpl;
	@Resource
	private ProjectTypeGradationDaoInter projecttypegradationDaoImpl;
	@Resource
	private FieldRePtypeDaoInter fieldreptypeDaoImpl;
	private static final Logger log = Logger.getLogger(ProjectTypeServiceImpl.class);

	@Override
	@Transactional
	public ProjectType insertProjecttypeEntity(ProjectType entity, LoginUser user) {
		entity.setCuser(user.getId());
		entity.setCtime(TimeTool.getTimeDate14());
		entity.setEuser(user.getId());
		entity.setEtime(TimeTool.getTimeDate14());
		entity.setPstate("1");
		if (StringUtils.isBlank(entity.getParentid())) {
			entity.setParentid("NONE");
		} else {
			ProjectType parentType = getProjecttypeEntity(entity.getParentid());
			if (parentType.getModel().equals("1")) {
				throw new RuntimeException("'类型'节点下禁止创建子节点!");
			}
		}
		entity.setTreecode("NONE");
		entity = projecttypeDaoImpl.insertEntity(entity);
		initTreeCode(entity.getId());
		return entity;
	}

	private void initTreeCode(String treeNodeId) {
		ProjectType node = getProjecttypeEntity(treeNodeId);
		if (node.getParentid().equals("NONE")) {
			node.setTreecode(node.getId());
		} else {
			node.setTreecode(projecttypeDaoImpl.getEntity(node.getParentid()).getTreecode() + node.getId());
		}
		projecttypeDaoImpl.editEntity(node);
	}

	@Override
	@Transactional
	public ProjectType editProjecttypeEntity(ProjectType entity, LoginUser user) {
		ProjectType entity2 = projecttypeDaoImpl.getEntity(entity.getId());
		// entity2.setEuser(user.getId());
		// entity2.setEusername(user.getName());
		// entity2.setEtime(TimeTool.getTimeDate14());
		entity2.setModel(entity.getModel());
		// entity2.setParentid(entity.getParentid());
		// entity2.setTreecode(entity.getTreecode());
		entity2.setName(entity.getName());
		entity2.setSort(entity.getSort());
		entity2.setPcontent(entity.getPcontent());
		entity2.setPstate(entity.getPstate());
		// entity2.setEuser(entity.getEuser());
		// entity2.setCuser(entity.getCuser());
		// entity2.setEtime(entity.getEtime());
		// entity2.setCtime(entity.getCtime());
		// entity2.setId(entity.getId());
		projecttypeDaoImpl.editEntity(entity2);
		return entity2;
	}

	@Override
	@Transactional
	public void deleteProjecttypeEntity(String id, LoginUser user) {
		if (projecttypeDaoImpl.selectEntitys(DBRule.addRule(new ArrayList<DBRule>(), "parentid", id, "=")).size() > 0) {
			throw new RuntimeException("不能删除该节点，请先删除其子节点");
		}
		fieldreptypeDaoImpl.deleteEntitys(DBRuleList.getInstance().add(new DBRule("PROJECTTYPEID", id, "=")).toList());
		projecttypegradationDaoImpl
				.deleteEntitys(DBRuleList.getInstance().add(new DBRule("PROJECTTYPEID", id, "=")).toList());
		projecttypeDaoImpl.deleteEntity(projecttypeDaoImpl.getEntity(id));
	}

	@Override
	@Transactional
	public ProjectType getProjecttypeEntity(String id) {
		// TODO 自动生成代码,修改后请去除本注释
		if (id == null) {
			return null;
		}
		return projecttypeDaoImpl.getEntity(id);
	}

	@Override
	@Transactional
	public DataQuery createProjecttypeSimpleQuery(DataQuery query) {
		DataQuery dbQuery = DataQuery.init(query,
				"( SELECT ID, NAME, SORT,PARENTID, MODEL, MODEL AS MODELVAL, PCONTENT, PSTATE, EUSER, CUSER, ETIME, CTIME,( SELECT COUNT(*) FROM PLOGS_RE_TYPEGRADATION WHERE PLOGS_RE_TYPEGRADATION.PROJECTTYPEID = PLOGS_PROJECT_TYPE.ID ) AS GRADATIONNUM FROM PLOGS_PROJECT_TYPE  ) A",
				"ID,SORT,NAME,MODEL,MODELVAL,PCONTENT,PSTATE,GRADATIONNUM");
		return dbQuery;
	}

	@Override
	@Transactional
	public void moveTreeNode(String ids, String targetId, LoginUser currentUser) {
		String[] idArray = ids.split(",");
		ProjectType target = getProjecttypeEntity(targetId);
		if (target != null && target.getModel().equals("1")) {
			throw new RuntimeException("'类型'节点下禁止创建子节点!");
		}
		for (int i = 0; i < idArray.length; i++) {
			// 移动节点
			ProjectType node = getProjecttypeEntity(idArray[i]);
			if (target != null && target.getTreecode().indexOf(node.getTreecode()) >= 0) {
				throw new RuntimeException("不能够移动到其子节点下!");
			}
			if (target == null) {
				node.setParentid("NONE");
			} else {
				node.setParentid(targetId);
			}
			projecttypeDaoImpl.editEntity(node);
			// 构造所有树TREECODE
			List<ProjectType> list = projecttypeDaoImpl.getAllSubNodes(idArray[i]);
			for (ProjectType org : list) {
				initTreeCode(org.getId());
			}
		}
	}

	@Override
	@Transactional
	public DataQuery createReGradationsQuery(DataQuery query, String projectTypeid) {
		DataQuery dbQuery = DataQuery.init(query,
				"PLOGS_RE_TYPEGRADATION a left join PLOGS_PROJECT_GRADATION b on b.ID=a.GRADATIONID",
				"A.ID AS ID,B.NAME AS NAME,A.SORT AS SORT,B.PCONTENT AS PCONTENT");
		return dbQuery;
	}

	@Override
	@Transactional
	public void bindGradation(String gradationid, String typeid, LoginUser currentUser) {
		projecttypegradationDaoImpl.deleteEntitys(DBRuleList.getInstance().add(new DBRule("PROJECTTYPEID", typeid, "="))
				.add(new DBRule("GRADATIONID", gradationid, "=")).toList());
		ProjectTypeGradation entity = new ProjectTypeGradation();
		ProjectGradation gradation = projectgradationDaoImpl.getEntity(gradationid);
		entity.setGradationid(gradationid);
		entity.setProjecttypeid(typeid);
		entity.setSort(gradation.getSort());
		projecttypegradationDaoImpl.insertEntity(entity);

	}

	@Override
	@Transactional
	public void rebindGradation(String id, LoginUser currentUser) {
		projecttypegradationDaoImpl.deleteEntity(projecttypegradationDaoImpl.getEntity(id));
	}

	@Override
	@Transactional
	public void toUpProjectTypeGradationSort(String reids, LoginUser currentUser) {
		List<ProjectTypeGradation> all = projecttypegradationDaoImpl.selectEntitys(DBRuleList.getInstance()
				.add(new DBRule("PROJECTTYPEID",
						projecttypegradationDaoImpl.getEntity(WebUtils.parseIds(reids).get(0)).getProjecttypeid(), "="))
				.toList());
		Collections.sort(all, new Comparator<ProjectTypeGradation>() {
			@Override
			public int compare(ProjectTypeGradation o1, ProjectTypeGradation o2) {
				return o1.getSort() - o2.getSort();
			}
		});
		Set<String> upids = new HashSet<>();
		for (String id : WebUtils.parseIds(reids)) {
			upids.add(id);
		}
		int n = 0;
		int firstN = 0;
		for (ProjectTypeGradation node : all) {
			n = n + 2;
			node.setSort(n);
			if (upids.contains(node.getId())) {
				if (firstN == 0) {
					firstN = n - 3;
				}
				node.setSort(firstN);
			}
		}
		Collections.sort(all, new Comparator<ProjectTypeGradation>() {
			@Override
			public int compare(ProjectTypeGradation o1, ProjectTypeGradation o2) {
				return o1.getSort() - o2.getSort();
			}
		});
		int m = 0;
		for (ProjectTypeGradation node : all) {
			node.setSort(++m);
			projecttypegradationDaoImpl.editEntity(node);
		}
	}

	@Override
	@Transactional
	public List<ProjectType> getAllTypes(String model) {
		DBRuleList rules = DBRuleList.getInstance();
		if (StringUtils.isNotBlank(model)) {
			rules.add(new DBRule("MODEL", model, "="));
		}
		return projecttypeDaoImpl.selectEntitys(rules.add(new DBRule("PSTATE", "1", "=")).toList());
	}

	@Override
	@Transactional
	public List<Field> getDataSearchFields(String typeid) {
		DataQuery dbQuery = DataQuery.getInstance(1,
				"b.ID as ID,b.CTIME as CTIME,b.ETIME as ETIME,b.CUSER as CUSER ,b.EUSER as EUSER ,b.PSTATE as PSTATE,b.PCONTENT as PCONTENT,b.NAME as NAME,b.TYPEID as TYPEID ,b.LIVETIME as LIVETIME ,b.VALTYPE as VALTYPE,b.UUID as UUID,b.SORT as SORT,b.SINGLETYPE as SINGLETYPE,b.ENUMS as ENUMS",
				"PLOGS_FIELD_REPTYPE a left join PLOGS_FIELD b on a.FIELDID=b.id");
		dbQuery.addSqlRule(" and SINGLETYPE='1' and a.PROJECTTYPEID='" + typeid + "' and READIS='1' and b.PSTATE='1'");
		dbQuery.addSqlRule(" and VALTYPE in ('4','5','6','9','10') ");
		dbQuery.addSort(new DBSort("a.SORT", "asc"));
		dbQuery.setNoCount();
		dbQuery.setPagesize(6);
		List<Field> result = null;
		try {
			result = dbQuery.search().getObjectList(Field.class);
		} catch (SQLException e) {
			e.printStackTrace();
			result = new ArrayList<>();
		}
		return result;
	}
}
